package com.cskaoyan.javase.oop1._13block._2building;

/**
 * 根据构造代码块的特点，分析一下它的实际使用场景。
 * 构造代码块最大的特点就是其中的代码，最终会加入类的所有构造器中，所以依据这一点：
 *
 * 我们可以"提取公因式"一样的，把所有构造器都需要执行的代码，放入构造代码块中。
 * 其次，构造代码块毕竟是给成员变量赋值用的，所以：
 *
 * 如果需要很复杂的代码完成成员变量的赋值（如果只是给一个值，用显式赋值和构造器足矣）
 * 比如需要一个算法，需要一定计算等等。在这些场景下，使用构造代码块赋值也是一个不错的选择。
 * 实际上,你可以把构造代码块看成是一个在创建对象过程中,自动被调用的成员方法.
 *
 * 思考:
 *      构造代码块可以给类的成员变量赋值,那么它可不可以给类的静态成员变量赋值?
 *      可以,当然可以
 *      因为静态成员变量在类加载之后就存在了
 *      而构造代码块在创建对象过程中执行,这时一定存在静态成员变量
 *
 *      但是这种给静态成员变量赋值的手段和类加载完全没有关系
 *      需要依赖于创建对象
 *      那么,如果我需要在类加载时期给静态成员变量赋值的代码块
 *      那就用静态代码块
 *
 * @since 16:01
 * @author wuguidong@cskaoyan.onaliyun.com
 */
public class Demo4 {
    public static void main(String[] args) {
        /*for (int i = 0; i < 3; i++) {
            new Teacher();
        }
        for (int i = 0; i < 3; i++) {
            new Teacher(18);
        }
        for (int i = 0; i < 4; i++) {
            new Teacher(18, "张三");
        }*/
        System.out.println(Teacher.count);
    }
}

class Teacher {
    int age;
    String name;
    static int count = 0;

    {
        age = 18;
        // 构造代码块中的代码会加入类的每个构造器(存在this调用别的构造器除外)
        count++;
    }

    public Teacher(int age) {
        this.age = age;
    }

    public Teacher() {
    }

    public Teacher(int age, String name) {
        this.age = age;
        this.name = name;
    }

}
